package com.witmore.skyline.web.utils.mapworld;

import com.alibaba.fastjson.JSONObject;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.Getter;
import lombok.Setter;

import java.io.IOException;
import java.net.URI;
import java.net.URLEncoder;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.nio.charset.StandardCharsets;

public class MapWorldReverseGeocoding {


    public static void main(String[] args) throws IOException, InterruptedException {
        ReverseGeocodeResponse reverseGeocodeResponse = reverseGeocodeHandle(116.397428, 39.90923);
        System.out.println(JSONObject.toJSONString(reverseGeocodeResponse));
    }
    public static ReverseGeocodeResponse reverseGeocodeHandle(double longitude, double latitude) throws IOException, InterruptedException {
        // 构建请求参数
        String postStr = String.format("{\"lon\":%.5f,\"lat\":%.5f,\"ver\":1}", longitude, latitude);
        String encodedPostStr = URLEncoder.encode(postStr, StandardCharsets.UTF_8);

        // 构建完整URL
        String url = String.format("%s?postStr=%s&type=geocode&tk=%s",
                MapWorldConstant.MAP_WORLD_API_URL, encodedPostStr, MapWorldConstant.API_KEY);

        // 创建HTTP客户端
        HttpClient client = HttpClient.newHttpClient();
        HttpRequest request = HttpRequest.newBuilder()
                .uri(URI.create(url))
                .GET()
                .build();

        // 发送请求并获取响应
        HttpResponse<String> response = client.send(request, HttpResponse.BodyHandlers.ofString());

        // 解析JSON响应
        ObjectMapper mapper = new ObjectMapper();
        return mapper.readValue(response.body(), ReverseGeocodeResponse.class);
    }

    public static String reverseGeocode(double longitude, double latitude) throws IOException, InterruptedException {
        ReverseGeocodeResponse response = reverseGeocodeHandle(longitude, latitude);
        if ("0".equals(response.getStatus())) {
            return response.getResult().getFormattedAddress();
        } else {
            throw new IOException("Reverse geocoding failed: " + response.getMsg());
        }
    }

    @Setter
    @Getter
    @JsonIgnoreProperties(ignoreUnknown = true)
    public static class ReverseGeocodeResponse {
        private Result result;
        private String status;
        private String msg;

    }

    @Setter
    @Getter
    @JsonIgnoreProperties(ignoreUnknown = true)
    public static class Result {
        @JsonProperty("formatted_address")
        private String formattedAddress;
        private Location location;
        @JsonProperty("addressComponent")
        private AddressComponent addressComponent;

    }

    @Setter
    @Getter
    public static class Location {
        private double lon;
        private double lat;

    }

    @Setter
    @Getter
    @JsonIgnoreProperties(ignoreUnknown = true)
    public static class AddressComponent {
        private String address;
        @JsonProperty("address_distance")
        private int addressDistance;
        @JsonProperty("address_position")
        private String addressPosition;
        private String city;
        private String poi;
        @JsonProperty("poi_distance")
        private int poiDistance;
        @JsonProperty("poi_position")
        private String poiPosition;
        private String road;
        @JsonProperty("road_distance")
        private int roadDistance;

    }
}
